package top.xtcoder.jdcbase.base.controller;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.codec.digest.DigestUtils;
import org.nutz.dao.Dao;
import org.nutz.filepool.FilePool;
import org.nutz.lang.Files;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.annotation.Order;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import cn.dev33.satoken.stp.StpUtil;
import cn.hutool.core.io.FileUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import top.xtcoder.jdcbase.base.common.Funs;
import top.xtcoder.jdcbase.base.core.Resp;
import top.xtcoder.jdcbase.base.entity.system.FileInfo;

@Api(tags = "文件池模块")
@RestController
@RequestMapping(value = "/jdcbase/prbase/file/pool")
public class PrBaseFilePoolController {
	@Autowired
	private FilePool pool;
	
	@Autowired
	private Dao dao;
	
	@SuppressWarnings("unchecked")
	@Order(value = 0)
	@ApiOperation(value="单文件上传方法-不保存到数据库",consumes="multipart/form-data")
	@ApiImplicitParams({
		@ApiImplicitParam(name="file",value="文件流数据",required = true,paramType = "form",dataType = "__File")
	})
	@PostMapping("/singleFiles")
	public Resp<FileInfo> singleFiles(
			@RequestParam(value="file",required = true) MultipartFile file
			,HttpServletRequest request){
		try {
			String fileName = file.getOriginalFilename();
			String contentType = file.getContentType();
			String suffix = "." + contentType.split("/")[1];
			File saveFile = pool.createFile(suffix);
			file.transferTo(saveFile);

			long id = pool.getFileId(saveFile);
			String url = "/jdcbase/prbase/file/pool/getFile/" + id + "/" +fileName;
			
			FileInfo data =new FileInfo();
			data.init();
			data.setName(fileName);
			data.setTitle(fileName);
			data.setPath(saveFile.getAbsolutePath());
			data.setFileMd5(DigestUtils.md5Hex(new FileInputStream(data.getPath())));
			data.setUrl(url);
			data.setSuffix(suffix);
			data.setContentType(contentType);
			data.setSize(saveFile.length());
			String userid = "DEFAULT";
			String usertype = "DEFAULT";
			try {
				userid = StpUtil.getLoginId().toString().substring(1);
				usertype = StpUtil.getLoginId().toString().substring(0,1);
			}catch(Exception e) {
				System.err.println("未登录用户上传，采用默认userid=DEFAULT");
			}
			data.setUserid(userid);
			
			return Resp.OK("上传成功", data);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
			return Resp.ERROR("上传失败");
		} 
	}
	
	@Order(value = 1)
	@ApiOperation(value="批量文件上传方法-不保存到数据库",consumes="multipart/form-data")
	@ApiImplicitParam(name="files",value="文件流数据",required = true,dataType = "__File",allowMultiple = true)
	@PostMapping("/batchFiles")
	public Resp<List<FileInfo>> batchFiles(MultipartFile[] files, HttpServletRequest request){
		if(files == null|| files.length <= 0) {
			return new Resp().error("文件列表为空");
		}
		try {
			//创建文件在服务器端存放路径
			List<FileInfo> fileInfos = new ArrayList<>();
			for(MultipartFile file : files) {
				String fileName = file.getOriginalFilename();
				String contentType = file.getContentType();
				String suffix = "." + contentType.split("/")[1];
				File saveFile = pool.createFile(suffix);
				file.transferTo(saveFile);

				long id = pool.getFileId(saveFile);
				String url = "/jdcbase/prbase/file/pool/getFile/" + id + "/" + fileName;
				
				FileInfo data =new FileInfo();
				data.init();
				data.setName(fileName);
				data.setTitle(fileName);
				data.setPath(saveFile.getAbsolutePath());
				data.setFileMd5(DigestUtils.md5Hex(new FileInputStream(data.getPath())));
				data.setUrl(url);
				data.setSuffix(suffix.replace(".", ""));
				data.setContentType(contentType);
				data.setSize(saveFile.length());
				String userid = "DEFAULT";
				String usertype = "DEFAULT";
				try {
					userid = StpUtil.getLoginId().toString().substring(1);
					usertype=StpUtil.getLoginId().toString().substring(0,1);
				}catch(Exception e) {
					System.err.println("未登录用户上传，采用默认userid=DEFAULT");
				}
				data.setUserid(userid);
				fileInfos.add(data);
			}
			return Resp.OK("上传成功", fileInfos);
		} catch (Exception e) {
			e.printStackTrace();
			return Resp.ERROR(e.getMessage());
		}
	}
	
	@SuppressWarnings("unchecked")
	@Order(value = 0)
	@ApiOperation(value="单文件上传方法-保存到数据库",consumes="multipart/form-data")
	@ApiImplicitParams({
		@ApiImplicitParam(name="file",value="文件流数据",required = true,paramType = "form",dataType = "__File")
	})
	@PostMapping("/singleFilesSaveDB")
	public Resp<FileInfo> singleFilesSaveDB(
			@RequestParam(value="file",required = true) MultipartFile file
			,HttpServletRequest request){
		try {
			Resp<FileInfo> resp = singleFiles(file, request);
			FileInfo data = (FileInfo) resp.getData().insertOrUpdate(dao);
			return Resp.OK("上传成功", data);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
			return Resp.ERROR("上传失败");
		} 
	}
	
	@Order(value = 1)
	@ApiOperation(value="批量文件上传方法-保存到数据库",consumes="multipart/form-data")
	@ApiImplicitParam(name="files",value="文件流数据",required = true,dataType = "__File",allowMultiple = true)
	@PostMapping("/batchFilesSaveDB")
	public Resp<List<FileInfo>> batchFilesSaveDB(MultipartFile[] files, HttpServletRequest request){
		if(files == null|| files.length <= 0) {
			return new Resp().error("文件列表为空");
		}
		try {
			//创建文件在服务器端存放路径
			Resp<List<FileInfo>> resp = batchFiles(files, request);
			List<FileInfo> fileInfos = resp.getData();
			fileInfos = dao.insert(fileInfos);
			return Resp.OK("上传成功", fileInfos);
		} catch (Exception e) {
			e.printStackTrace();
			return Resp.ERROR(e.getMessage());
		}
	}
	
	@ApiOperation(value="文件获取")
	@GetMapping("/getFile/{id}/{name}")
	public void getFile(
		@ApiParam(name="id",required = true)
		@PathVariable(name="id",required = true) 
		long id,
		
		@ApiParam(name="name",required = true)
		@PathVariable(name="name",required = true) 
		String name,
	
		HttpServletRequest request,
		HttpServletResponse response) throws IllegalStateException, IOException {
		System.out.println("id=" + id + ", name=" + name);
		String suffix = Files.getSuffix(name);
		File file = pool.getFile(id, suffix);
		
		byte[] fileBdata =FileUtil.readBytes(file);
		OutputStream os = response.getOutputStream();
		os.write(fileBdata);
		os.flush();
		os.close();
	}
}
